#include "placecircletool.h"
#include "item/circleitem.h"
#include "command/additemcommand.h"
#include "view/scene.h"

#include <QGraphicsSceneMouseEvent>
#include <QLineF>

namespace SymbolEditor
{

    PlaceCircleTool::PlaceCircleTool(QObject *parent):
        AbstractTool(parent),
        m_state(WaitingForActivation),
        m_item(nullptr)
    {
        setLabel("<b>P</b>lace a <b>C</b>ircle");
        setShortcut(QKeySequence("p,c"));
        setIcon(QIcon::fromTheme("draw-circle"));
        updateAction();
    }

    PlaceCircleTool::~PlaceCircleTool()
    {
    }

    void PlaceCircleTool::addItem()
    {
        m_item = new GraphicsCircleItem();
        m_item->setEnabled(false);
        scene()->addItem(m_item);
    }

    void PlaceCircleTool::updateItem()
    {
        m_item->setProperty(PositionProperty, m_p1);
        m_item->setProperty(RadiusProperty, QLineF(m_p1, m_p2).length());
    }

    void PlaceCircleTool::removeItem()
    {
        scene()->removeItem(m_item);
        delete m_item;
    }

    bool PlaceCircleTool::mouseClickEvent(QGraphicsSceneMouseEvent *event)
    {
        switch (m_state)
        {
            case WaitingForActivation:
                break;
            case WaitingForCenter:
            {
                m_p1 = m_p2 = event->scenePos();
                addItem();
                updateItem();
                m_state = WaitingForRadius;
                break;
            }
            case WaitingForRadius:
            {
                m_p2 = event->scenePos();
                updateItem();
                m_item->setEnabled(true);

                auto command = new AddItemCommand();
                command->setItemType(Circle); // FIXME: typeForDocument()
                command->setItemProperties(m_item->properties());
                appendCommand(command);

                removeItem();
                m_state = WaitingForCenter;
                break;
            }
        }
        return true;
    }

    bool PlaceCircleTool::mouseMoveEvent(QGraphicsSceneMouseEvent *event)
    {
        switch (m_state)
        {
            case WaitingForActivation:
                break;
            case WaitingForCenter:
                break;
            case WaitingForRadius:
                m_p2 = event->scenePos();
                updateItem();
                break;
        }
        return true;
    }

    void PlaceCircleTool::activate(Scene *scene)
    {
        if (m_state != WaitingForActivation)
        {
            desactivate();
        }
        setScene(scene);
        m_p1 = m_p2 = QPointF();
        m_state = WaitingForCenter;
    }

    void PlaceCircleTool::desactivate()
    {
        switch (m_state)
        {
            case WaitingForActivation:
            case WaitingForCenter:
                break;
            case WaitingForRadius:
                removeItem();
                break;
        }
        setScene(nullptr);
        m_state = WaitingForActivation;
    }

}
